home *** CD-ROM | disk | FTP | other *** search
/ Amiga Collections: Taifun / Taifun 086 (1989-02-15)(Ossowski, Stefan)(DE)(PD).zip / Taifun 086 (1989-02-15)(Ossowski, Stefan)(DE)(PD).adf / FiveInLine / FiveInLine.c < prev    next >
C/C++ Source or Header  |  1988-12-10  |  10KB  |  500 lines

  1. #include "exec/types.h"
  2. #include "intuition/intuition.h"
  3. #include "stdio.h"
  4. #include "string.h"
  5.  
  6. struct IntuitionBase *IntuitionBase;
  7. struct GfxBase *GfxBase;
  8. struct RastPort *r,*r2;
  9. struct Window *Wind,*abWind;
  10. struct NewWindow NewWindow,NewWindow2;
  11. struct IntuiMessage *mesg;
  12. struct IntuiText prompt,yprompt,t0,t1;
  13. struct Menu Menu1;
  14. struct MenuItem m0,m1;
  15.  
  16. #define INTUITION_REV 29
  17. #define GRAPHICS_REV  29
  18. #define n             19
  19.  
  20. BOOL    gamewon=FALSE,firstmove=TRUE;
  21. USHORT  mclass,mcode,msx,msy;
  22. SHORT   d,i,j,k,l,x,y,amx,amy,start;
  23. SHORT   lx,ly,pla,opp,x0,x1,y0,y1,max,value;
  24. SHORT   AttackFactor;
  25. SHORT   Board[n+1][n+1],Aline[4][n+1][n+1][2],Value[n+1][n+1][2];
  26. int     ov,xv,len;
  27. char    text[10];
  28. static  SHORT Weight[]={0,0,4,20,100,500,0};
  29.  
  30. VOID _main()
  31. {
  32.  
  33.     VOID OpenALL(),Human(),AddUp(),UpdateValue(),MakeMove(),FindMove();
  34.     VOID CreateMes(),DrawFrame(),make_window(),init_newgame();
  35.     VOID setup_menu(),show_About();
  36.  
  37.     AttackFactor=4;
  38.     start=0;
  39.  
  40.     OpenALL();
  41.     make_window();
  42.  
  43.     setup_menu();
  44.     SetMenuStrip(Wind,&Menu1);
  45.  
  46.     r=Wind->RPort;
  47.  
  48.     CreateMes(&yprompt,3,3," OK ");
  49.  
  50. NewGame:
  51.  
  52.     init_newgame();
  53.     if(start == 0) goto Human_first;
  54.  
  55. Loop:
  56.     pla=1;
  57.     opp=0;
  58.     FindMove();
  59.     MakeMove();
  60.     Board[x][y]=2;
  61.  
  62.     if (! firstmove) {
  63.         SetAPen(r,0);
  64.         DrawFrame();
  65.     }
  66.     else firstmove=FALSE;
  67.  
  68.     x0=(x-1)*20;
  69.     y0=(y-1)*8;
  70.     SetAPen(r,1);
  71.     Move(r,x0+14,y0+14);
  72.     Draw(r,x0+26,y0+18);
  73.     Move(r,x0+14,y0+18);
  74.     Draw(r,x0+26,y0+14);
  75.  
  76.     amx=x0+13;
  77.     amy=y0+13;
  78.     SetAPen(r,3);
  79.     DrawFrame();
  80.  
  81.     if (gamewon) {
  82.         ov=ov+1;
  83.  
  84.         CreateMes(&prompt,50,5,"I won");
  85.         AutoRequest(Wind,&prompt,&yprompt,&yprompt,NULL,NULL,160,50);
  86.  
  87.         goto NewGame;
  88.     }
  89.  
  90. Human_first:
  91.  
  92.     pla=0;
  93.     opp=1;
  94.     Human();
  95.     MakeMove();
  96.  
  97.     if (gamewon) {
  98.         xv=xv+1;
  99.         CreateMes(&prompt,37,5,"You won!");
  100.         AutoRequest(Wind,&prompt,&yprompt,&yprompt,NULL,NULL,160,50);
  101.  
  102.         goto NewGame;
  103.     }
  104.  
  105.     goto Loop;
  106. }
  107.  
  108.  
  109. VOID Human()
  110.  
  111. {
  112.     /* Set Up an IDCMP Read Loop */
  113. HumanLoop:
  114.     Wait (1 << Wind->UserPort->mp_SigBit);
  115.  
  116.     while((mesg=(struct IntuiMessage *) GetMsg(Wind->UserPort)) != NULL) {
  117.         mclass=mesg->Class;
  118.         mcode=mesg->Code;
  119.         msx=mesg->MouseX;
  120.         msy=mesg->MouseY;
  121.         ReplyMsg(mesg);
  122.     }
  123.  
  124.     switch(mclass) {
  125.         case MENUPICK: {
  126.             if(ITEMNUM(mcode) == 0) {
  127.                 ClearMenuStrip(Wind);
  128.                 show_About();
  129.  
  130.                 while((mesg=(struct IntuiMessage *) GetMsg(Wind->UserPort)) != NULL) ReplyMsg(mesg);
  131.  
  132.                 SetMenuStrip(Wind,&Menu1);
  133.                 goto HumanLoop;
  134.             }
  135.             else if(ITEMNUM(mcode) == 1) {                 /* Quit */
  136.                 ClearMenuStrip(Wind);
  137.                 CloseWindow(Wind);
  138.                 exit(FALSE);
  139.                 break;
  140.             }
  141.             else goto HumanLoop;
  142.         }
  143.         case MOUSEBUTTONS: {
  144.             if(ReadPixel(r,msx,msy) == 2) goto HumanLoop;  /* black line */
  145.             if(msx < 10 || msx > 10+n*20) goto HumanLoop;  /* outside board */
  146.             if(msy < 12 || msy > 12+n*8) goto HumanLoop;   /* outside board */
  147.  
  148.             y=((msy-12)/8)+1;
  149.             x=((msx-10)/20)+1;
  150.             if(Board[x][y] > 0) goto HumanLoop;            /* occupied square */
  151.  
  152.             Board[x][y]=1;
  153.             i=(x-1)*20+16;
  154.             j=y*8+6;
  155.  
  156.             SetAPen(r,1);
  157.             Move(r,i+1,j);
  158.             Draw(r,i+6,j);
  159.             Move(r,i+7,j+1);
  160.             Draw(r,i+7,j+3);
  161.             Move(r,i+6,j+4);
  162.             Draw(r,i+1,j+4);
  163.             Move(r,i,j+3);
  164.             Draw(r,i,j+1);
  165.         }
  166.     }
  167. }
  168.  
  169.  
  170. VOID MakeMove()
  171.  
  172. {
  173.     gamewon=FALSE;
  174.  
  175.     d=0;
  176.     for(k=0;k<=4;k++) {
  177.         x1=x-k;
  178.         y1=y;
  179.         if(x1>=1 && x1<=n-4) {
  180.             AddUp();
  181.             for(l=0;l<=4;l++)
  182.                 UpdateValue();
  183.         }
  184.     }
  185.  
  186.     d=1;
  187.     for(k=0;k<=4;k++) {
  188.         x1=x-k;
  189.         y1=y-k;
  190.         if((x1>=1 && x1<=n-4) && (y1>=1 && y1<=n-4)) {
  191.             AddUp();
  192.             for(l=0;l<=4;l++)
  193.                 UpdateValue();
  194.         }
  195.     }
  196.  
  197.     d=3;
  198.     for(k=0;k<=4;k++) {
  199.         x1=x+k;
  200.         y1=y-k;
  201.         if((x1>=5 && x1 <= n) && (y1>=1 && y1<=n-4)) {
  202.             AddUp();
  203.             for(l=0;l<=4;l++)
  204.                 UpdateValue();
  205.         }
  206.     }
  207.  
  208.     d=2;
  209.     for(k=0;k<=4;k++) {
  210.         x1=x;
  211.         y1=y-k;
  212.         if(y1>=1 && y1<=n-4) {
  213.             AddUp();
  214.             for(l=0;l<=4;l++)
  215.                 UpdateValue();
  216.         }
  217.     }
  218. }
  219.  
  220.  
  221. VOID AddUp()
  222.  
  223. {
  224.     Aline[d][x1][y1][pla] = Aline[d][x1][y1][pla] + 1;
  225.  
  226.     if(Aline[d][x1][y1][pla] == 5) gamewon=TRUE;
  227. }
  228.  
  229.  
  230. VOID UpdateValue()
  231.  
  232. {
  233.     if(d==0) {
  234.         lx=l;
  235.         ly=0;
  236.     }
  237.     else if(d==1) {
  238.         lx=l;
  239.         ly=l;
  240.     }
  241.     else if(d==2) {
  242.         lx=0;
  243.         ly=l;
  244.     }
  245.     else {
  246.         lx=-l;
  247.         ly=l;
  248.     }
  249.  
  250.     if(Aline[d][x1][y1][opp] == 0) Value[x1+lx][y1+ly][pla] = Value[x1+lx][y1+ly][pla] + Weight[Aline[d][x1][y1][pla]+1] - Weight[Aline[d][x1][y1][pla]];
  251.     else if(Aline[d][x1][y1][pla] == 1) Value[x1+lx][y1+ly][opp] = Value[x1+lx][y1+ly][opp] - Weight[Aline[d][x1][y1][opp]+1];
  252. }
  253.  
  254.  
  255. VOID FindMove()
  256.  
  257. {
  258.     max=-32767;
  259.     x=(n+1)/2;
  260.     y=(n+1)/2;
  261.     if(Board[x][y] == 0) max=4;
  262.  
  263.     for(i=1;i<=n;i++)   {
  264.         for(j=1;j<=n;j++) {
  265.             if(Board[i][j] == 0) {
  266.                 value=Value[i][j][pla] * (16 + AttackFactor) / 16 + Value[i][j][opp];
  267.                 if(value > max) {
  268.                     x=i;
  269.                     y=j;
  270.                     max=value;
  271.                 }
  272.             }
  273.         }
  274.     }
  275. }
  276.  
  277.  
  278. VOID OpenALL()        /* Open required libraries */
  279.  
  280. {
  281.     IntuitionBase=(struct IntuitionBase *) OpenLibrary("intuition.library",INTUITION_REV);
  282.  
  283.     if(IntuitionBase == NULL) exit(FALSE);
  284.  
  285.     GfxBase=(struct GfxBase *) OpenLibrary("graphics.library",GRAPHICS_REV);
  286.  
  287.     if(GfxBase == NULL) exit(FALSE);
  288. }
  289.  
  290.  
  291. VOID CreateMes(x,left,top,mes)
  292.  
  293. struct  IntuiText *x;
  294. SHORT   left,top;
  295. UBYTE   *mes;
  296. {
  297.     x->FrontPen=0;
  298.     x->BackPen=1;
  299.     x->DrawMode=JAM1;
  300.     x->LeftEdge=left;
  301.     x->TopEdge=top;
  302.     x->ITextFont=NULL;
  303.     x->IText=mes;
  304.     x->NextText=NULL;
  305. }
  306.  
  307.  
  308. VOID DrawFrame()
  309.  
  310. {
  311.     Move(r,amx,amy);
  312.     Draw(r,amx+14,amy);
  313.     Draw(r,amx+14,amy+6);
  314.     Draw(r,amx,amy+6);
  315.     Draw(r,amx,amy);
  316. }
  317.  
  318.  
  319. VOID make_window()        /* Open a plain window */
  320.  
  321. {
  322.     NewWindow.LeftEdge=0;
  323.     NewWindow.TopEdge=0;
  324.     NewWindow.Width=480;
  325.     NewWindow.Height=170;
  326.     NewWindow.DetailPen=-1;
  327.     NewWindow.BlockPen=-1;
  328.     NewWindow.Title="Five In Line";
  329.     NewWindow.Flags=ACTIVATE|WINDOWDRAG|WINDOWDEPTH|SMART_REFRESH;
  330.     NewWindow.IDCMPFlags=MOUSEBUTTONS|MENUPICK;
  331.     NewWindow.Type=WBENCHSCREEN;
  332.     NewWindow.FirstGadget=NULL;
  333.     NewWindow.CheckMark=NULL;
  334.     NewWindow.Screen=NULL;
  335.     NewWindow.BitMap=NULL;
  336.     NewWindow.MinWidth=0;
  337.     NewWindow.MinHeight=0;
  338.     NewWindow.MaxWidth=640;
  339.     NewWindow.MaxHeight=200;
  340.  
  341.     Wind=(struct Window *) OpenWindow(&NewWindow);
  342.  
  343. }
  344.  
  345.  
  346. VOID init_newgame()
  347.  
  348. {
  349.     start=1-start;                /* toggle between computer and human */
  350.  
  351.     for(x=1;x<=n;x++) {
  352.         for(y=1;y<=n;y++)
  353.             Board[x][y]=0;
  354.     }
  355.  
  356.     for(d=0;d<=3;d++) {
  357.         for(x=1;x<=n;x++) {
  358.             for(y=1;y<=n;y++) {
  359.                 for(pla=0;pla<=1;pla++)
  360.                     Aline[d][x][y][pla]=0;
  361.             }
  362.         }
  363.     }
  364.  
  365.     for(x=1;x<=n;x++) {
  366.         for(y=1;y<=n;y++) {
  367.             for(pla=0;pla<=1;pla++)
  368.                 Value[x][y][pla]=0;
  369.         }
  370.     }
  371.  
  372.     SetAPen(r,0);
  373.     RectFill(r,10,12,400,168);        /* blank board           */
  374.  
  375.     firstmove=TRUE;
  376.  
  377. /* draw new grid */
  378.  
  379.     SetAPen(r,2);
  380.  
  381.     for(x=10;x<=10+n*20;x=x+20) {
  382.         Move(r,x,12);
  383.         Draw(r,x,12+n*8);
  384.     }
  385.  
  386.     for(y=12;y<=12+n*8;y=y+8) {
  387.         Move(r,10,y);
  388.         Draw(r,10+n*20,y);
  389.     }
  390.  
  391. /* print scores */
  392.  
  393.     SetAPen(r,1);
  394.     Move(r,420,30);
  395.     Text(r,"You:",4);
  396.     Move(r,450,30);
  397.     len=sprintf(text,"%3d",xv);
  398.     Text(r,text,len);
  399.  
  400.     Move(r,420,45);
  401.     Text(r,"I  :",4);
  402.     Move(r,450,45);
  403.     len=sprintf(text,"%3d",ov);
  404.     Text(r,text,len);
  405. }
  406.  
  407.  
  408. VOID setup_menu()
  409.  
  410. {
  411.     CreateMes(&t0,0,0,"About");
  412.  
  413.     m0.NextItem=&m1;
  414.     m0.LeftEdge=5;
  415.     m0.TopEdge=0;
  416.     m0.Width=50;
  417.     m0.Height=10;
  418.     m0.Flags=ITEMTEXT|HIGHCOMP|ITEMENABLED;
  419.     m0.MutualExclude=NULL;
  420.     m0.ItemFill=(APTR)&t0;
  421.     m0.SelectFill=NULL;
  422.     m0.Command=NULL;
  423.     m0.SubItem=NULL;
  424.  
  425.     CreateMes(&t1,0,0,"Quit");
  426.  
  427.     m1.NextItem=NULL;
  428.     m1.LeftEdge=5;
  429.     m1.TopEdge=15;
  430.     m1.Width=50;
  431.     m1.Height=10;
  432.     m1.Flags=ITEMTEXT|HIGHCOMP|ITEMENABLED;
  433.     m1.MutualExclude=NULL;
  434.     m1.ItemFill=(APTR)&t1;
  435.     m1.SelectFill=NULL;
  436.     m1.Command=NULL;
  437.     m1.SubItem=NULL;
  438.  
  439.     Menu1.NextMenu=NULL;
  440.     Menu1.LeftEdge=0;
  441.     Menu1.TopEdge=0;
  442.     Menu1.Width=60;
  443.     Menu1.Height=100;
  444.     Menu1.Flags=MENUENABLED;
  445.     Menu1.MenuName="Project";
  446.     Menu1.FirstItem=&m0;
  447.  
  448. }
  449.  
  450.  
  451. VOID show_About()
  452.  
  453. {
  454.     NewWindow2.LeftEdge=Wind->LeftEdge + 40;
  455.     NewWindow2.TopEdge=Wind->TopEdge + 45;
  456.     NewWindow2.Width=400;
  457.     NewWindow2.Height=80;
  458.     NewWindow2.DetailPen=-1;
  459.     NewWindow2.BlockPen=-1;
  460.     NewWindow2.Title="About Five In Line";
  461.     NewWindow2.Flags=ACTIVATE|WINDOWCLOSE|SMART_REFRESH;
  462.     NewWindow2.IDCMPFlags=CLOSEWINDOW;
  463.     NewWindow2.Type=WBENCHSCREEN;
  464.     NewWindow2.FirstGadget=NULL;
  465.     NewWindow2.CheckMark=NULL;
  466.     NewWindow2.Screen=NULL;
  467.     NewWindow2.BitMap=NULL;
  468.     NewWindow2.MinWidth=0;
  469.     NewWindow2.MinHeight=0;
  470.     NewWindow2.MaxWidth=640;
  471.     NewWindow2.MaxHeight=200;
  472.  
  473.     abWind=(struct Window *) OpenWindow(&NewWindow2);
  474.     r2=abWind->RPort;
  475.  
  476.     SetAPen(r2,1);
  477.     Move(r2,10,20);
  478.     Text(r2,"Placed in Public Domain 1988",28);
  479.     Move(r2,10,30);
  480.     Text(r2,"by Njål Fisketjøn.",18);
  481.  
  482.     Move(r2,10,50);
  483.     Text(r2,"Algorithm from a",16);
  484.  
  485.     SetAPen(r2,3);
  486.     Move(r2,146,50);
  487.     Text(r2,"Borland Turbo Pascal",20);
  488.  
  489.     SetAPen(r2,1);
  490.     Move(r2,314,50);
  491.     Text(r2,"program.",8);
  492.  
  493.     Move(r2,10,70);
  494.     Text(r2,"Close window to continue playing.",33);
  495.  
  496.     Wait (1 << abWind->UserPort->mp_SigBit);
  497.     while((mesg=(struct IntuiMessage *) GetMsg(abWind->UserPort)) != NULL) ReplyMsg(mesg);
  498.     CloseWindow(abWind);
  499. }
  500.